home *** CD-ROM | disk | FTP | other *** search
/ OpenGL Superbible (2nd Edition) / OpenGL SuperBible e2.iso / tools / GLUT-3.7 / PROGS / advanced97 / ACCUMAA.C < prev    next >
Encoding:
C/C++ Source or Header  |  1998-08-12  |  6.5 KB  |  273 lines

  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <GL/glut.h>
  4.  
  5. const GLdouble FRUSTDIM = 100.f;
  6.  
  7. /*
  8. ** Create a single component texture map
  9. */
  10. GLfloat *make_texture(int maxs, int maxt)
  11. {
  12.     int s, t;
  13.     static GLfloat *texture;
  14.  
  15.     texture = (GLfloat *)malloc(maxs * maxt * sizeof(GLfloat));
  16.     for(t = 0; t < maxt; t++) {
  17.     for(s = 0; s < maxs; s++) {
  18.         texture[s + maxs * t] = ((s >> 4) & 0x1) ^ ((t >> 4) & 0x1);
  19.     }
  20.     }
  21.     return texture;
  22. }
  23.  
  24. enum {SPHERE = 1, CONE};
  25.  
  26. void
  27. render(void)
  28. {
  29.     /* material properties for objects in scene */
  30.     static GLfloat wall_mat[] = {1.f, 1.f, 1.f, 1.f};
  31.  
  32.     glClear(GL_DEPTH_BUFFER_BIT|GL_COLOR_BUFFER_BIT);
  33.  
  34.     /*
  35.     ** Note: wall verticies are ordered so they are all front facing
  36.     ** this lets me do back face culling to speed things up.
  37.     */
  38.  
  39.     glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, wall_mat);
  40.  
  41.     /* floor */
  42.     /* make the floor textured */
  43.     glEnable(GL_TEXTURE_2D);
  44.  
  45.     /*
  46.     ** Since we want to turn texturing on for floor only, we have to
  47.     ** make floor a separate glBegin()/glEnd() sequence. You can't
  48.     ** turn texturing on and off between begin and end calls
  49.     */
  50.     glBegin(GL_QUADS);
  51.     glNormal3f(0.f, 1.f, 0.f);
  52.     glTexCoord2i(0, 0);
  53.     glVertex3f(-100.f, -100.f, -320.f);
  54.     glTexCoord2i(1, 0);
  55.     glVertex3f( 100.f, -100.f, -320.f);
  56.     glTexCoord2i(1, 1);
  57.     glVertex3f( 100.f, -100.f, -520.f);
  58.     glTexCoord2i(0, 1);
  59.     glVertex3f(-100.f, -100.f, -520.f);
  60.     glEnd();
  61.  
  62.     glDisable(GL_TEXTURE_2D);
  63.  
  64.     /* walls */
  65.  
  66.     glBegin(GL_QUADS);
  67.     /* left wall */
  68.     glNormal3f(1.f, 0.f, 0.f);
  69.     glVertex3f(-100.f, -100.f, -320.f);
  70.     glVertex3f(-100.f, -100.f, -520.f);
  71.     glVertex3f(-100.f,  100.f, -520.f);
  72.     glVertex3f(-100.f,  100.f, -320.f);
  73.  
  74.     /* right wall */
  75.     glNormal3f(-1.f, 0.f, 0.f);
  76.     glVertex3f( 100.f, -100.f, -320.f);
  77.     glVertex3f( 100.f,  100.f, -320.f);
  78.     glVertex3f( 100.f,  100.f, -520.f);
  79.     glVertex3f( 100.f, -100.f, -520.f);
  80.  
  81.     /* ceiling */
  82.     glNormal3f(0.f, -1.f, 0.f);
  83.     glVertex3f(-100.f,  100.f, -320.f);
  84.     glVertex3f(-100.f,  100.f, -520.f);
  85.     glVertex3f( 100.f,  100.f, -520.f);
  86.     glVertex3f( 100.f,  100.f, -320.f);
  87.  
  88.     /* back wall */
  89.     glNormal3f(0.f, 0.f, 1.f);
  90.     glVertex3f(-100.f, -100.f, -520.f);
  91.     glVertex3f( 100.f, -100.f, -520.f);
  92.     glVertex3f( 100.f,  100.f, -520.f);
  93.     glVertex3f(-100.f,  100.f, -520.f);
  94.     glEnd();
  95.  
  96.  
  97.     glPushMatrix();
  98.     glTranslatef(-80.f, -60.f, -420.f);
  99.     glCallList(SPHERE);
  100.     glPopMatrix();
  101.  
  102.  
  103.     glPushMatrix();
  104.     glTranslatef(-20.f, -80.f, -500.f);
  105.     glCallList(CONE);
  106.     glPopMatrix();
  107.  
  108.     if(glGetError()) /* to catch programming errors; should never happen */
  109.     printf("Oops! I screwed up my OpenGL calls somewhere\n");
  110.  
  111.     glFlush(); /* high end machines may need this */
  112. }
  113.  
  114. /* compute scale factor for window->object space transform */
  115. /* could use gluUnProject(), but probably too much trouble */
  116. void
  117. computescale(GLfloat *sx, GLfloat *sy)
  118. {
  119.     enum {XORG, YORG, WID, HT};
  120.     GLint viewport[4];
  121.     glGetIntegerv(GL_VIEWPORT, viewport);
  122.  
  123.     *sx = 2 * FRUSTDIM/viewport[WID];
  124.     *sy = 2 * FRUSTDIM/viewport[WID];
  125. }
  126.  
  127. enum {NONE, AA};
  128.  
  129. int rendermode = NONE;
  130.  
  131. void
  132. menu(int selection)
  133. {
  134.     rendermode = selection;
  135.     glutPostRedisplay();
  136. }
  137.  
  138. /* Called when window needs to be redrawn */
  139. void redraw(void)
  140. {
  141.     int i, j;
  142.     int min, max;
  143.     int count;
  144.     GLfloat invx, invy;
  145.     GLfloat scale, dx, dy;
  146.  
  147.     switch(rendermode) {
  148.     case NONE:
  149.     glMatrixMode(GL_PROJECTION);
  150.     glLoadIdentity();
  151.     glFrustum(-FRUSTDIM, FRUSTDIM, -FRUSTDIM, FRUSTDIM, 320., 640.); 
  152.     glMatrixMode(GL_MODELVIEW);
  153.     render();
  154.     break;
  155.     case AA:
  156.     min = -2;
  157.     max = -min + 1;
  158.     count = -2 * min + 1;
  159.     count *= count;
  160.  
  161.     /* uniform scaling, less than one pixel wide */
  162.     scale = -.9f/min;
  163.  
  164.     computescale(&invx, &invy);
  165.  
  166.     glutSetCursor(GLUT_CURSOR_WAIT);
  167.  
  168.     glClear(GL_ACCUM_BUFFER_BIT);
  169.  
  170.     for(j = min; j < max; j++) {
  171.         for(i = min; i < max; i++) {
  172.         printf("pass %d of %d\n",
  173.                (j-min)*(max-min)+i-min+1,(max-min)*(max-min));
  174.         dx = invx * scale * i;
  175.         dy = invy * scale * j;
  176.         glMatrixMode(GL_PROJECTION);
  177.         glLoadIdentity();
  178.         glFrustum(-FRUSTDIM + dx, 
  179.               FRUSTDIM + dy, 
  180.               -FRUSTDIM + dx, 
  181.               FRUSTDIM + dy, 
  182.               320., 640.); 
  183.         glMatrixMode(GL_MODELVIEW);
  184.         render();
  185.         glAccum(GL_ACCUM, 1.f/count);
  186.         }
  187.     }
  188.     glAccum(GL_RETURN, 1.f);
  189.     glutSetCursor(GLUT_CURSOR_INHERIT);
  190.     break;
  191.     }
  192.  
  193.     glutSwapBuffers();
  194. }
  195.  
  196. void key(unsigned char key, int x, int y)
  197. {
  198.     if(key == '\033')
  199.     exit(0);
  200. }
  201.  
  202.  
  203. const int TEXDIM = 256;
  204. /* Parse arguments, and set up interface between OpenGL and window system */
  205. main(int argc, char *argv[])
  206. {
  207.     GLfloat *tex;
  208.     static GLfloat lightpos[] = {50.f, 50.f, -320.f, 1.f};
  209.     static GLfloat sphere_mat[] = {1.f, .5f, 0.f, 1.f};
  210.     static GLfloat cone_mat[] = {0.f, .5f, 1.f, 1.f};
  211.     GLUquadricObj *sphere, *cone, *base;
  212.  
  213.     glutInitWindowSize(512, 512);
  214.     glutInit(&argc, argv);
  215.     glutInitDisplayMode(GLUT_RGBA|GLUT_DEPTH|GLUT_ACCUM|GLUT_DOUBLE);
  216.     (void)glutCreateWindow("Anti-aliasing with Accum");
  217.     glutDisplayFunc(redraw);
  218.     glutKeyboardFunc(key);
  219.  
  220.     glutCreateMenu(menu);
  221.     glutAddMenuEntry("Aliased View", NONE);
  222.     glutAddMenuEntry("AntiAliased", AA);
  223.     glutAttachMenu(GLUT_RIGHT_BUTTON);
  224.  
  225.     /* draw a perspective scene */
  226.     glMatrixMode(GL_PROJECTION);
  227.     glFrustum(-FRUSTDIM, FRUSTDIM, -FRUSTDIM, FRUSTDIM, 320., 640.); 
  228.     glMatrixMode(GL_MODELVIEW);
  229.  
  230.     /* turn on features */
  231.     glEnable(GL_DEPTH_TEST);
  232.     glEnable(GL_LIGHTING);
  233.     glEnable(GL_LIGHT0);
  234.  
  235.     /* place light 0 in the right place */
  236.     glLightfv(GL_LIGHT0, GL_POSITION, lightpos);
  237.  
  238.     /* remove back faces to speed things up */
  239.     glCullFace(GL_BACK);
  240.  
  241.     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
  242.  
  243.     glNewList(SPHERE, GL_COMPILE);
  244.     /* make display lists for sphere and cone; for efficiency */
  245.     sphere = gluNewQuadric();
  246.     glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, sphere_mat);
  247.     gluSphere(sphere, 20.f, 20, 20);
  248.     gluDeleteQuadric(sphere);
  249.     glEndList();
  250.  
  251.     glNewList(CONE, GL_COMPILE);
  252.     cone = gluNewQuadric();
  253.     base = gluNewQuadric();
  254.     glRotatef(-90.f, 1.f, 0.f, 0.f);
  255.     glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, cone_mat);
  256.     gluDisk(base, 0., 20., 20, 1);
  257.     gluCylinder(cone, 20., 0., 60., 20, 20);
  258.     gluDeleteQuadric(cone);
  259.     gluDeleteQuadric(base);
  260.     glEndList();
  261.  
  262.     /* load pattern for current 2d texture */
  263.     tex = make_texture(TEXDIM, TEXDIM);
  264.     glTexImage2D(GL_TEXTURE_2D, 0, 1, TEXDIM, TEXDIM, 0, GL_RED, GL_FLOAT, tex);
  265.     free(tex);
  266.  
  267.     glReadBuffer(GL_BACK); /* input to accum buffer */
  268.  
  269.     glutMainLoop();
  270.  
  271.     return 0;
  272. }
  273.